package com.runchinaup.smartbelt.domian;

import android.bluetooth.BluetoothAdapter;
import android.bluetooth.BluetoothGatt;
import android.bluetooth.BluetoothGattCallback;
import android.bluetooth.BluetoothGattCharacteristic;
import android.bluetooth.BluetoothGattDescriptor;
import android.bluetooth.BluetoothGattService;
import android.text.format.Time;
import android.util.Log;

import com.runchinaup.smartbelt.ble.BlueGattCallbackHelper;
import com.runchinaup.smartbelt.ble.NotificationType;

import java.io.Serializable;
import java.util.Timer;
import java.util.TimerTask;
import java.util.UUID;

import static com.runchinaup.smartbelt.App.getApp;

/**
 * Created by liber on 2018/2/1.
 */

public class BleDevice implements Serializable {

    private String Name;
    private String Address;
    private BluetoothGatt bluetoothGatt;
    private BluetoothGattCharacteristic bluetoothGattCharacteristic;
    private boolean connFlag = false;

    public String getName() {
        return Name;
    }

    public void setName(String name) {
        Name = name;
    }

    public String getAddress() {
        return Address;
    }

    public void setAddress(String address) {
        Address = address;
    }

    public BluetoothGatt getBluetoothGatt() {
        return bluetoothGatt;
    }

    public void setBluetoothGatt(BluetoothGatt bluetoothGatt) {
        this.bluetoothGatt = bluetoothGatt;
    }

    public BleDevice(String name, String address) {
        Name = name;
        Address = address;
    }

    BlueGattCallbackHelper.OnBleClickListenter onBleClickListenter;

    public void linkBle(BlueGattCallbackHelper.OnBleClickListenter onBleClickListenter) {
        this.onBleClickListenter = onBleClickListenter;
        BluetoothAdapter.getDefaultAdapter().getRemoteDevice(getAddress())
                .connectGatt(getApp(), false, linkCallback);
    }

    private boolean isHndDis = false;

    public void disBlueConnect() {
        isHndDis = true;
        PhoneCallAndMessage phoneCallAndMessage = new PhoneCallAndMessage();
        sendData(phoneCallAndMessage.closePhoneLoose());
        bluetoothGatt.disconnect();
        bluetoothGatt.close();
    }

    public void sendData(byte[] data) {
        bluetoothGattCharacteristic.setValue(data);
        bluetoothGatt.writeCharacteristic(bluetoothGattCharacteristic);
    }

    //同步时间
    public void synchronizationTime() {
        Time t = new Time();
        t.setToNow();
        int year = (t.year % 2000);
        int month = t.month + 1;
        int day = t.monthDay;
        int hour = t.hour;
        int minutes = t.minute;
        int second = t.second;

        byte[] timeValue = new byte[]{
                (byte) 0xa1,
                0x5a,
                0x0a,
                0x06,
                (byte) year,
                (byte) month,
                (byte) day,
                (byte) hour,
                (byte) minutes,
                (byte) second,
                0};
        //计算校验码
        int sum = 0;
        for (int i = 0; i < timeValue.length; i++) {
            sum = sum + timeValue[i];
        }
        int data = 0 - (sum % 256);
        byte dataByte = (byte) data;
        timeValue[timeValue.length - 1] = dataByte;
        //发送数据
        sendData(timeValue);
        Log.e("synchronizationTime: ", "同步时间");
    }

    //打开提示的开关
    public void _enable_notify_(BluetoothGatt gatt, BluetoothGattCharacteristic characteristic, NotificationType type) {
        BluetoothGattDescriptor descriptor = characteristic.getDescriptor(UUID.fromString("00002902-0000-1000-8000-00805f9b34fb"));
        if (descriptor == null) return;
        switch (type) {
            case DISABLE:
                gatt.setCharacteristicNotification(characteristic, false);
                descriptor.setValue(BluetoothGattDescriptor.DISABLE_NOTIFICATION_VALUE);
                break;
            case NOTIFICATION:
                gatt.setCharacteristicNotification(characteristic, true);
                descriptor.setValue(BluetoothGattDescriptor.ENABLE_NOTIFICATION_VALUE);
                break;
            case INDICATION:
                gatt.setCharacteristicNotification(characteristic, true);
                descriptor.setValue(BluetoothGattDescriptor.ENABLE_INDICATION_VALUE);
                break;
        }
        gatt.writeDescriptor(descriptor);
    }

    private void close(BluetoothGatt gatt) {
        if (gatt != null) {
            gatt.close();
        }
    }

    //ble连接的回调
    final BluetoothGattCallback linkCallback = new BluetoothGattCallback() {

        @Override
        public void onConnectionStateChange(final BluetoothGatt gatt, final int status, final int newState) {
            super.onConnectionStateChange(gatt, status, newState);
            bluetoothGatt = gatt;
            Log.e("debug:status", status + "");
            Log.e("derbu:newState", newState + "");

            if (status == BluetoothGatt.GATT_SUCCESS) {
                if (newState == BluetoothGatt.STATE_CONNECTED) {
                    connFlag = true;
                    isHndDis = false;       //是否由用户手动断开
                    Log.e("onConnectionStateChange", isHndDis + "");
                    onBleClickListenter.onState(1);     //连接成功是1
                    new Timer().schedule(new TimerTask() {
                        @Override
                        public void run() {
                            gatt.discoverServices();
                        }
                    }, 200);
                } else if (newState == BluetoothGatt.STATE_DISCONNECTED) {
                    Log.e("newState_disconn", isHndDis + "");
                    if (!isHndDis) {
                        onBleClickListenter.onExceptionDis(BleDevice.this);
                    }
                    if (connFlag) {
                        onBleClickListenter.onState(2);             //连接断开判断
                        Log.e("newState_disconn", "unlink");
                        close(gatt);
                    } else {// 连接超时
                        onBleClickListenter.onState(0);              //连接失败判断
                        Log.e("newState_disconn", "fail");
                    }
                }
            } else if (status == 133) {
                if (!isHndDis) {
                    onBleClickListenter.onExceptionDis(BleDevice.this);
                }
                onBleClickListenter.onState(133);              //意外断开
                Log.e("status_disconn", isHndDis + "");
            } else {
                Log.e("status_else_disconn", isHndDis + "");
                if (!isHndDis) {
                    onBleClickListenter.onExceptionDis(BleDevice.this);
                }
                if (connFlag) {
                    onBleClickListenter.onState(2);             //连接断开判断                            Log.e("onConnectionStateChange","unlink");
                    Log.e("status_else_disconn", "unlink");
                    close(gatt);
                } else {
                    onBleClickListenter.onState(0);              //连接失败判断
                    Log.e("status_else_disconn", "fail");
                }
            }

        }

        @Override
        public void onServicesDiscovered(final BluetoothGatt gatt, int status) {
            super.onServicesDiscovered(gatt, status);
            if (status != BluetoothGatt.GATT_SUCCESS) {
                gatt.disconnect();
                gatt.close();
                Log.e("onServicesDiscovered", "发现服务失败");
                return;
            } else {
                for (BluetoothGattService service : gatt.getServices()) {
                    for (BluetoothGattCharacteristic characteristic : service.getCharacteristics()) {
                        if (characteristic.getUuid().equals(UUID.fromString("0000fff4-0000-1000-8000-00805f9b34fb"))) {
                            bluetoothGattCharacteristic = characteristic;
                            _enable_notify_(gatt, characteristic, NotificationType.NOTIFICATION);
                            new Timer().schedule(new TimerTask() {
                                @Override
                                public void run() {
                                    //发送同步时间的指令
                                    synchronizationTime();
                                }
                            }, 1000);
                            onBleClickListenter.onLink(BleDevice.this);
                            break;
                        }
                    }
                }
            }
        }

        @Override
        public void onCharacteristicChanged(BluetoothGatt gatt, BluetoothGattCharacteristic characteristic) {
            super.onCharacteristicChanged(gatt, characteristic);
            byte[] data = characteristic.getValue();
            if (onBleClickListenter != null) {
                StringBuilder sb = new StringBuilder();
                for (byte b : data) {
                    sb.append(String.format("%02x", (b & 0xff)));
                }
                Log.e("onCharacteristicChanged", sb.toString());
                //获取电量
                if (0xa1 == (data[0] & 0xff)) {
                    if (0xa5 == (data[1] & 0xff)) {
                        if (0x0a == (data[2] & 0xff)) {
                            if (0x10 == (data[3] & 0xff)) {
                                onBleClickListenter.getElectricity(data);
                                Log.e("onChanged:", "get data");
                            }
                        }
                    }
                }

                //获取设备闹钟使能
                if (0xa1 == (data[0] & 0xff)) {
                    if (0xa5 == (data[1] & 0xff)) {
                        if (0x08 == (data[2] & 0xff)) {
                            if (0x50 == (data[3] & 0xff)) {
                                onBleClickListenter.getAlarmCan(data);
                                Log.e("getAlarmCan", "get alarm data");
                            }
                        }
                    }
                }

                //获取设备闹钟时间
                if (0xa1 == (data[0] & 0xff)) {
                    if (0xa5 == (data[1] & 0xff)) {
                        if (0x09 == (data[2] & 0xff)) {
                            if (0x40 == (data[3] & 0xff)) {
                                onBleClickListenter.getAlarmTime(data);
                                Log.e("getAlarmTime", "alarm time data");
                            }
                        }
                    }
                }

            }
        }
    };


}

